home *** CD-ROM | disk | FTP | other *** search
/ Aminet 25 / Aminet 25 (1998)(GTI - Schatztruhe)[!][Jun 1998].iso / Aminet / util / pack / xpk_Source.lha / xpk_Source / xpkmaster / open.c < prev    next >
C/C++ Source or Header  |  1998-03-27  |  16KB  |  508 lines

  1. #ifndef XPKMASTER_OPEN_C
  2. #define XPKMASTER_OPEN_C
  3.  
  4. /* Routinesheader
  5.  
  6.     Name:        open.c
  7.     Main:        xpkmaster
  8.     Versionstring:    $VER: open.c 1.16 (26.03.1998)
  9.     Author:        SDI
  10.     Distribution:    Freeware
  11.     Description:    Opening and initialisation routines for XPK files
  12.  
  13.  1.0   06.10.96 : first real version
  14.  1.1   28.10.96 : reincluded A4 support
  15.  1.2   03.03.97 : added Prefs, corrected length recognition
  16.  1.3   07.03.97 : fixed prefs handling, new features
  17.  1.4   09.03.97 : added DEBUG statement
  18.  1.5   28.03.97 : auto decrunch password
  19.  1.6   29.03.97 : fixed prefs stuff, moved getinlen into hooks
  20.  1.7   31.03.97 : changed the password stuff
  21.  1.8   19.12.97 : added xfdmaster.library support
  22.  1.9   22.12.97 : fixed auto password problem
  23.  1.10  27.12.97 : fixed GetPassword error
  24.  1.11  09.01.98 : better key handling
  25.  1.12  21.01.98 : added password verification for packing
  26.  1.13  24.01.98 : fixed xfdmaster support a bit
  27.  1.14  17.02.98 : fixe long file problem added in last version
  28.  1.15  21.02.98 : uses new style register definition
  29.  1.16  26.03.98 : some optimizations
  30. */
  31.  
  32. #include <xpk/xpkprefs.h>
  33. #include <exec/memory.h>
  34. #include <proto/exec.h>
  35. #include <proto/dos.h>
  36. #include <proto/xpkmaster.h>
  37. #include <proto/xpksub.h>
  38. #include <proto/xfdmaster.h>
  39. #include "xpkmaster.h"
  40. #include "texts.h"
  41.  
  42. static const struct XpkInfo DONTInfo = { 1,0,0,1,"DONT","Copy",
  43. 0, 0x55534552, XPKIF_PK_CHUNK|XPKIF_UP_CHUNK, DEFAULTCHUNKSIZE, 1,
  44. DEFAULTCHUNKSIZE,0,0,0,0,100,0,0,0,0,0,0,0,0};
  45. /* XpkMode is not initialized! Should not be used anywhere */
  46.  
  47. static LONG xpkopenwrite(struct XpkBuffer **, struct TagItem *);
  48. static LONG GetPrefsPacker(struct XpkBuffer *);
  49. static LONG GetPassword(struct XpkBuffer *, struct TagItem *, ULONG);
  50. static struct XpkTypeData *BufRecog(ULONG, struct XpkBuffer *,
  51.   struct XpkPrefsSemaphore *);
  52.  
  53. XPK_ALLINONE ASM(LONG) xpkopen(REG(a0, struct XpkBuffer **xbufp),
  54. REG(a1, struct TagItem *tags), REG(d2, ULONG examine A4PROTO))
  55. {
  56.   struct XpkBuffer     *xbuf;
  57.   struct XpkStreamHeader *globhdr;
  58.   struct XpkFib         *fib;
  59.  
  60. #if defined(DEBUG) && defined(SUPPORT_A4)
  61.   DebugRunTime("xpkopen: A4 = %ld", a4);
  62. #elif defined (DEBUG)
  63.   DebugRunTime("xpkopen");
  64. #endif
  65.  
  66.   if(!(*xbufp = xbuf = initxbuf()))
  67.     return parseerrortags(tags, XPKERR_NOMEM);
  68.  
  69. #ifdef SUPPORT_A4
  70.   xbuf->xb_regA4 = a4;
  71. #endif
  72.  
  73.   globhdr = &xbuf->xb_Headers.h_Glob;
  74.   fib = &xbuf->xb_Fib;
  75.  
  76.   if(parsebuftags(xbuf, tags))
  77.     goto Abort;
  78.  
  79.   if(xbuf->xb_Flags & XMF_PACKING) /* Call pack open function */
  80.     return xpkopenwrite(xbufp, tags);
  81.  
  82.   if(!hookread(xbuf, XIO_READ, globhdr, 4)) /* Read first longword */
  83.   {
  84.     if(xbuf->xb_Result != XPKERR_TRUNCATED)
  85.       goto Abort;
  86.     /* else handle now as uncompressed file */
  87.   }
  88.  
  89.   /***************************** Standard XPK file **********************/
  90.   if(globhdr->xsh_Pack == XPK_COOKIE)
  91.   {
  92.     UWORD exthlen = 0;        /* size of extended header if present */
  93.     struct Library * XpkSubBase;
  94.  
  95.     xbuf->xb_Format = XPKMODE_UPSTD;
  96.  
  97.     /* Read rest of the global header */
  98.     if(!hookread(xbuf, XIO_READ, (STRPTR) globhdr + 4, sizeof(struct XpkStreamHeader) - 4))
  99.       goto Abort;
  100.  
  101.     if(hchecksum((STRPTR) globhdr, sizeof(struct XpkStreamHeader)))
  102.     {
  103.       xbuf->xb_Result = XPKERR_CHECKSUM;
  104.       goto Abort;
  105.     }
  106.  
  107.     if(globhdr->xsh_Flags & XPKSTREAMF_LONGHEADERS)
  108.       xbuf->xb_Headers.h_LocSize = sizeof(struct XpkChunkHdrLong);
  109.     else
  110.       xbuf->xb_Headers.h_LocSize = sizeof(struct XpkChunkHdrWord);
  111.  
  112.     if(globhdr->xsh_Flags & XPKSTREAMF_EXTHEADER)
  113.     {
  114.       if(!hookread(xbuf, XIO_READ, &exthlen, sizeof(UWORD)))
  115.     goto Abort;
  116.       if(!hookread(xbuf, XIO_READ, NULL, exthlen))
  117.     goto Abort;
  118.       exthlen += sizeof(UWORD);    /* for unwinding while XpkExamine */
  119.     }
  120.  
  121.     if(!hookread(xbuf, XIO_READ, &xbuf->xb_Headers.h_Loc,
  122.     xbuf->xb_Headers.h_LocSize))    /* first lochdr */
  123.       goto Abort;
  124.  
  125.     fib->xf_CCur = sizeof(struct XpkStreamHeader);
  126.     updatefib(xbuf);
  127.     xbuf->xb_InLen = fib->xf_CLen;
  128.  
  129.     if(!(XpkSubBase = opensub(xbuf, globhdr->xsh_Type)))
  130.       goto Abort;
  131.  
  132.     if(globhdr->xsh_SubVrs > xbuf->xb_SubInfo->xi_LibVersion)
  133.     {
  134.       xbuf->xb_Result = XPKERR_OLDSUBLIB;
  135.       goto Abort;
  136.     }
  137.  
  138.     xbuf->xb_Prog.xp_Activity = xbuf->xb_SubInfo->xi_UnpackMsg ?
  139.       xbuf->xb_SubInfo->xi_UnpackMsg : strings[TXT_UNPACKING_UPPER];
  140.     xbuf->xb_Prog.xp_PackerName = xbuf->xb_SubInfo->xi_Name;
  141.     xbuf->xb_LastMsg = xbuf->xb_SubInfo->xi_UnpackedMsg ?
  142.       xbuf->xb_SubInfo->xi_UnpackedMsg : strings[TXT_UNPACKED];
  143.  
  144.     if(globhdr->xsh_Flags & XPKSTREAMF_PASSWORD)
  145.       fib->xf_Flags |= XPKFLAGS_PASSWORD;
  146.  
  147.     if(examine && !hookread(xbuf, XIO_SEEK, 0,
  148.     -(sizeof(struct XpkStreamHeader) + xbuf->xb_Headers.h_LocSize+exthlen)))
  149.       goto Abort;
  150.  
  151.     goto Exit;
  152.   }
  153.  
  154.   if(!hookread(xbuf, XIO_SEEK, 0, -xbuf->xb_RMsg.xmm_Size))
  155.     goto Abort; /* redo last read bytes */
  156.  
  157.   if(xbuf->xb_InLen == -1)
  158.   {
  159.     if(!hookread(xbuf, XIO_TOTSIZE, 0, 0))    /* get input length */
  160.       goto Abort;
  161.     else if(xbuf->xb_RMsg.xmm_Size)
  162.       xbuf->xb_InLen = xbuf->xb_RMsg.xmm_Size;
  163.   }
  164.  
  165.   fib->xf_CLen = xbuf->xb_InLen;
  166.  
  167. #ifdef USE_POWERPACKER
  168.   /***************************** PowerPacker file ***********************/
  169.   if(globhdr->xsh_Pack == PP_COOKIE)
  170.   {
  171.     ULONG outsize;
  172.  
  173.     xbuf->xb_Format = XPKMODE_UPPP;
  174.  
  175.     if(!hookread(xbuf, XIO_SEEK, 0, xbuf->xb_InLen - 4))
  176.       goto Abort;                /* 4 Bytes before EOF */
  177.     if(!hookread(xbuf, XIO_READ, &outsize, 4))
  178.       goto Abort;
  179.     if(!hookread(xbuf, XIO_SEEK, 0, - (xbuf->xb_InLen - 4) - (examine<<2)))
  180.       goto Abort;    /* back to start when examine, else 4 bytes later */
  181.  
  182.     outsize >>= 8;
  183.  
  184. #ifdef DEBUG
  185.     DebugRunTime("xpkopen: PP, InLen %ld, OutLen %ld", xbuf->xb_InLen,
  186.     outsize);
  187. #endif
  188.  
  189.     fib->xf_Type = XPKTYPE_PACKED;
  190.     fib->xf_ULen = outsize;
  191.     fib->xf_NLen = outsize + XPK_MARGIN;
  192.     fib->xf_ID = PP_COOKIE;
  193.     percentages(fib);
  194.     xbuf->xb_Prog.xp_Activity = strings[TXT_UNPACKING_UPPER];
  195.     xbuf->xb_Prog.xp_PackerName = "PowerPacker";
  196.     xbuf->xb_LastMsg = strings[TXT_UNPACKED];
  197.  
  198.     if(!examine && !(xbuf->xb_SubBase = OpenLibrary("powerpacker.library", 0)))
  199.     {
  200.       xbuf->xb_Result = XPKERR_MISSINGLIB;
  201.       goto Abort;
  202.     }
  203.  
  204.     goto Exit;
  205.   }
  206. #endif /* USE_POWERPACKER */
  207.  
  208.   /**************************** xfdmaster file **************************/
  209.   if(xbuf->xb_Flags & XMF_XFD &&
  210.   (xbuf->xb_SubBase = OpenLibrary("xfdmaster.library", 38)))
  211.   {
  212.     struct xfdMasterBase *xfdMasterBase = (struct xfdMasterBase *) xbuf->xb_SubBase;
  213.     struct xfdBufferInfo *xbi;
  214.  
  215.     if(!(xbi = xbuf->xb_xfd = (struct xfdBufferInfo *) xfdAllocObject(XFDOBJ_BUFFERINFO)))
  216.       goto Abort;
  217.     if(!(xbi->xfdbi_SourceBuffer = hookread(xbuf, XIO_READ, 0, xbuf->xb_InLen)))
  218.       goto Abort;
  219.     xbi->xfdbi_SourceBufLen = xbuf->xb_InLen;
  220.     xbi->xfdbi_Flags = XFDFF_RECOGEXTERN|XFDFF_RECOGTARGETLEN|XFDFF_RECOGUSERTARGET;
  221.  
  222.     if(xfdRecogBuffer(xbi) && (xbi->xfdbi_PackerFlags & XFDPFF_DATA) &&
  223.     (LONG) xbi->xfdbi_FinalTargetLen != -1)
  224.     {
  225.       xbuf->xb_Format = XPKMODE_UPXFD;
  226.       if(xbi->xfdbi_PackerFlags & XFDPFF_PASSWORD)
  227.         xbuf->xb_Fib.xf_Flags |= XPKFLAGS_PASSWORD;
  228.       if(xbi->xfdbi_PackerFlags & XFDPFF_KEY16)
  229.         xbuf->xb_Fib.xf_Flags |= XPKFLAGS_KEY16;
  230.       if(xbi->xfdbi_PackerFlags & XFDPFF_KEY32)
  231.         xbuf->xb_Fib.xf_Flags |= XPKFLAGS_KEY32;
  232.       fib->xf_Type = XPKTYPE_PACKED;
  233.       fib->xf_ULen = xbi->xfdbi_FinalTargetLen;
  234.       fib->xf_NLen = xbi->xfdbi_MinTargetLen;
  235.       fib->xf_ID = XFD_COOKIE;
  236.       percentages(fib);
  237.       xbuf->xb_Prog.xp_Activity = strings[TXT_UNPACKING_UPPER];
  238.       xbuf->xb_Prog.xp_PackerName = "XFDMaster";
  239.       xbuf->xb_LastMsg = strings[TXT_UNPACKED];
  240.  
  241.       if(examine && !hookread(xbuf, XIO_SEEK, 0, -xbuf->xb_InLen))
  242.         goto Abort; /* return to start */
  243.  
  244. #ifdef DEBUG
  245.       DebugRunTime("xpkopen: XFD, InLen %ld, OutLen %ld, NLen %ld",
  246.       xbuf->xb_InLen, fib->xf_ULen, fib->xf_NLen);
  247. #endif
  248.       goto Exit;
  249.     } /* xfdRecogBuffer */
  250.  
  251.     if(!hookread(xbuf, XIO_SEEK, 0, -xbuf->xb_InLen))
  252.       goto Abort; /* return to start */
  253.   }
  254.  
  255.   /*************************** Uncompressed file ************************/
  256.   if(examine || xbuf->xb_Flags & XMF_PASSTHRU)        /* Unpacked */
  257.   {
  258.     xbuf->xb_Format = XPKMODE_UPUP;
  259.  
  260.     fib->xf_Type = XPKTYPE_UNPACKED;
  261.     fib->xf_ULen = xbuf->xb_InLen;
  262.     fib->xf_NLen = Min(DEFAULTCHUNKSIZE, xbuf->xb_InLen) + XPK_MARGIN;
  263.     fib->xf_ID = ROW_OF_MINUS;
  264.  
  265.     xbuf->xb_Prog.xp_Activity = strings[TXT_READING];
  266.     xbuf->xb_Prog.xp_PackerName = "Master";
  267.     xbuf->xb_LastMsg = strings[TXT_READ];
  268.  
  269.     xbuf->xb_Result = XPKERR_OK;  /* if != 0 it was XPKERR_TRUNCATED */
  270.  
  271.     goto Exit;
  272.   }
  273.  
  274.   xbuf->xb_Result = XPKERR_NOTPACKED;    /* Can't unpack, can't passthru */
  275.  
  276. Abort:
  277.   *xbufp = 0;
  278.   return XpkClose((struct XpkFib *) xbuf);
  279.  
  280. Exit:
  281.   if(!examine && (
  282.   ((fib->xf_Flags & XPKFLAGS_PASSWORD) && !xbuf->xb_Password) ||
  283.   ((fib->xf_Flags & XPKFLAGS_KEY16) && !(xbuf->xb_Flags & XMF_KEY16)) ||
  284.   ((fib->xf_Flags & XPKFLAGS_KEY32) && !(xbuf->xb_Flags & XMF_KEY32)))
  285.   && (xbuf->xb_Result = GetPassword(xbuf, tags, FALSE)))
  286.       goto Abort;
  287.   return XPKERR_OK;
  288. }
  289.  
  290. /***************************** Open for packing *************************/
  291. static LONG xpkopenwrite(struct XpkBuffer **xbufp, struct TagItem *tags)
  292. {
  293.   struct XpkBuffer        *xbuf        = *xbufp;
  294.   struct XpkStreamHeader    *globhdr    = &xbuf->xb_Headers.h_Glob;
  295.   struct Library        *XpkSubBase;
  296.   LONG                 res;
  297.  
  298.   xbuf->xb_Format = XPKMODE_PKSTD;
  299.  
  300.   if(xbuf->xb_InLen == -1)
  301.   {
  302.     if(!hookread(xbuf, XIO_TOTSIZE, 0, 0))    /* get input length */
  303.       return xbuf->xb_Result;
  304.     else if(xbuf->xb_RMsg.xmm_Size)
  305.       xbuf->xb_InLen = xbuf->xb_RMsg.xmm_Size;
  306.   }
  307.  
  308.   if(!(XpkSubBase = xbuf->xb_SubBase) &&  /* Do we know the sublib? */
  309.   (xbuf->xb_Result = GetPrefsPacker(xbuf)))
  310.     goto Abort; /* no sublib and no prefs packer finder */
  311.  
  312.   if(xbuf->xb_Password && !(xbuf->xb_SubInfo->xi_Flags & XPKIF_ENCRYPTION))
  313.   {
  314.     xbuf->xb_Result = XPKERR_NOCRYPT;
  315.     goto Abort;
  316.   }
  317.  
  318.   if(!xbuf->xb_Password && (xbuf->xb_SubInfo->xi_Flags & XPKIF_NEEDPASSWD))
  319.   { /* automatic password requester */
  320.     if((xbuf->xb_Result = GetPassword(xbuf, tags, TRUE)))
  321.       goto Abort;
  322.   }
  323.  
  324.   if(!(xbuf->xb_Flags & XMF_LOSSYOK) &&
  325.   xbuf->xb_SubInfo->xi_Flags & XPKIF_LOSSY)
  326.   {
  327.     xbuf->xb_Result = XPKERR_LOSSY;
  328.     goto Abort;
  329.   }
  330.  
  331.   if(xbuf->xb_PackingMode > 100)    /* Is packing mode valid? */
  332.     xbuf->xb_PackingMode = 100;        /* Use max */
  333.  
  334.   if(!hookwrite(xbuf, XIO_TOTSIZE, 0, ROUNDLONG
  335.   (xbuf->xb_InLen + (xbuf->xb_InLen >> 5)) + (XPK_MARGIN<<1)))
  336.     goto Abort;
  337.  
  338.   /************************* Find the chunk size ************************/
  339.   if((xbuf->xb_ChunkSize == 0) &&
  340.   ((xbuf->xb_ChunkSize = xbuf->xb_SubInfo->xi_DefPkInChunk) == 0))
  341.     xbuf->xb_ChunkSize = DEFAULTCHUNKSIZE;
  342.   if(xbuf->xb_ChunkSize < xbuf->xb_SubInfo->xi_MinPkInChunk)
  343.     xbuf->xb_ChunkSize = xbuf->xb_SubInfo->xi_MinPkInChunk;
  344.   if((xbuf->xb_SubInfo->xi_MaxPkInChunk) &&
  345.   (xbuf->xb_ChunkSize > xbuf->xb_SubInfo->xi_MaxPkInChunk))
  346.     xbuf->xb_ChunkSize = xbuf->xb_SubInfo->xi_MaxPkInChunk;
  347.  
  348.   /************************ Prepare global header ***********************/
  349.   globhdr->xsh_Pack = 0;        /* Initialize the global header */
  350.   globhdr->xsh_Type = xbuf->xb_SubID;
  351.  
  352.   if(xbuf->xb_ChunkSize > 65000) /* (0xFFFF-XPK_MARGIN) and some bytes security */
  353.     globhdr->xsh_Flags |= XPKSTREAMF_LONGHEADERS;
  354.   if(xbuf->xb_Password)
  355.     globhdr->xsh_Flags |= XPKSTREAMF_PASSWORD;
  356.  
  357.   xbuf->xb_Headers.h_LocSize = globhdr->xsh_Flags & XPKSTREAMF_LONGHEADERS
  358.     ? sizeof (struct XpkChunkHdrLong)
  359.     : sizeof (struct XpkChunkHdrWord);
  360.  
  361.   memset(globhdr->xsh_Initial, 0xff, 16);    /* Read first 16 bytes */
  362.  
  363.   xbuf->xb_Prog.xp_Activity = xbuf->xb_SubInfo->xi_PackMsg ?
  364.   xbuf->xb_SubInfo->xi_PackMsg : strings[TXT_PACKING_UPPER];
  365.   xbuf->xb_Prog.xp_PackerName = xbuf->xb_SubInfo->xi_Name;
  366.   xbuf->xb_LastMsg = xbuf->xb_SubInfo->xi_PackedMsg ?
  367.   xbuf->xb_SubInfo->xi_PackedMsg : strings[TXT_PACKED];
  368.  
  369. Abort:
  370.   xbuf->xb_Fib.xf_NLen = Min(xbuf->xb_InLen - xbuf->xb_Fib.xf_UCur,
  371.   xbuf->xb_ChunkSize);
  372.  
  373.   if((res = xbuf->xb_Result))
  374.     res = XpkClose((struct XpkFib *) xbuf);
  375.  
  376.   return res;
  377. }
  378.  
  379. typedef ASM(struct XpkTypeData *) (*RecogFunc) (REG(a0, STRPTR),
  380.     REG(a1, STRPTR), REG(d0, ULONG), REG(d1, ULONG),
  381.     REG(a2, struct TagItem *));
  382.  
  383. static LONG GetPrefsPacker(struct XpkBuffer *xbuf)
  384. {
  385.   LONG ret = XPKERR_UNKNOWN;
  386.   struct XpkPrefsSemaphore *sem;
  387.   ULONG bufsize;
  388.   struct XpkTypeData *td = 0;
  389.  
  390.   if(xbuf->xb_Flags & XMF_NOPREFS)
  391.     return XPKERR_BADPARAMS;
  392.   if(!(sem = GetPrefsSem()))
  393.     return XPKERR_NOFUNC;
  394.  
  395.   bufsize = Min(xbuf->xb_InLen, sem->xps_RecogSize);
  396.  
  397.   if(sem->xps_RecogFunc && (td = BufRecog(bufsize, xbuf, sem)) ==
  398.   (struct XpkTypeData *) 0xFFFFFFFF)
  399.     td = BufRecog(xbuf->xb_InLen, xbuf, sem);
  400.  
  401.   if(!td || td == (struct XpkTypeData *) 0xFFFFFFFF)
  402.     td = sem->xps_MainPrefs ? sem->xps_MainPrefs->xmp_DefaultType : 0;
  403.  
  404.   if(td)
  405.   {
  406.     if(td->xtd_Flags & XTD_NoPack)
  407.     {
  408.       xbuf->xb_Flags |= XMF_NOPACK;
  409.       xbuf->xb_SubInfo = (struct XpkInfo *) &DONTInfo;
  410.       ret = XPKERR_OK;
  411.     }
  412.     else if(!(td->xtd_Flags & XTD_ReturnError))
  413.     {
  414.       struct Library *XpkSubBase;
  415.       struct XpkInfo *subinfo;
  416.  
  417.       if((XpkSubBase = opensub(xbuf, td->xtd_StdID)))
  418.       {
  419.     ret = XPKERR_OK;
  420.         subinfo = XpksPackerInfo();
  421.  
  422.         xbuf->xb_ChunkSize = td->xtd_ChunkSize;
  423.         xbuf->xb_PackingMode = ( td->xtd_Mode ? td->xtd_Mode :
  424.           subinfo->xi_DefMode);
  425. //    if(!(xbuf->xb_Password) && td->xtd_Password && 
  426. //    (xbuf->xb_PasswordSize = strlen(td->xtd_Password)))
  427. //    {
  428. //      /* we need a buffer including end byte! --> ++size */
  429. //      if(!(xbuf->xb_Password = (STRPTR)
  430. //      AllocMem(++xbuf->xb_PasswordSize, MEMF_PUBLIC)))
  431. //        ret = XPKERR_NOMEM;
  432. //        else
  433. //      {
  434. //        xbuf->Flags |= XMF_OWNPASSWORD;
  435. //        CopyMem(td->xtd_Password, xbuf->xb_Password, xbuf->xb_PasswordSize);
  436. //      }
  437. //    }
  438.       }
  439.     }
  440.     else
  441.       ret = XPKERR_NOMETHOD;
  442.   }
  443.  
  444.   if(td->xtd_Memory && td->xtd_MemorySize)
  445.     FreeMem(td->xtd_Memory, td->xtd_MemorySize);
  446.  
  447.   ReleaseSemaphore((struct SignalSemaphore *) sem);
  448.   return ret;
  449. }
  450.  
  451. static LONG GetPassword(struct XpkBuffer *xbuf, struct TagItem *tags,
  452. ULONG verify)
  453. {
  454.  if(xbuf->xb_Flags & XMF_AUTOPASSWD)
  455.  {
  456.    if(xbuf->xb_Fib.xf_Flags & XPKFLAGS_KEY32)
  457.    {
  458.      xbuf->xb_Result = XpkPassRequestTags(XPK_Key32BitPtr,
  459.      &xbuf->xb_PassKey32, TAG_MORE, tags, TAG_DONE);
  460.      xbuf->xb_Flags |= XMF_KEY32;
  461.    }
  462.    else if(xbuf->xb_Fib.xf_Flags & XPKFLAGS_KEY16)
  463.    {
  464.      xbuf->xb_Result = XpkPassRequestTags(XPK_Key16BitPtr,
  465.      &xbuf->xb_PassKey16, TAG_MORE, tags, TAG_DONE);
  466.      xbuf->xb_Flags |= XMF_KEY16;
  467.    }
  468.    else
  469.    {
  470.      if(!(xbuf->xb_Password = (STRPTR) AllocMem(AUTO_PASS_SIZE, MEMF_PUBLIC)))
  471.        return XPKERR_NOMEM;
  472.      xbuf->xb_PasswordSize = AUTO_PASS_SIZE;
  473.      xbuf->xb_Flags |= XMF_OWNPASSWORD; /* must be freed later */
  474.  
  475.      xbuf->xb_Result = XpkPassRequestTags(XPK_PasswordBuf,
  476.      xbuf->xb_Password, XPK_PassBufSize, xbuf->xb_PasswordSize,
  477.      XPK_PassVerify, verify, TAG_MORE, tags, TAG_DONE);
  478.    }
  479.  
  480.    return xbuf->xb_Result;
  481.  }
  482.  return XPKERR_NEEDPASSWD;
  483. }
  484.  
  485. static struct XpkTypeData *BufRecog(ULONG bufsize, struct XpkBuffer *xbuf,
  486. struct XpkPrefsSemaphore *sem)
  487. {
  488.   STRPTR bufptr;
  489.   struct XpkTypeData *ret = 0;
  490.   struct TagItem tag[] = {
  491.   { XPK_FileName, 0},
  492.   { XPK_PackMode, 0},
  493.   { TAG_DONE, 0}};
  494.  
  495.   tag[0].ti_Data = (ULONG) xbuf->xb_Prog.xp_FileName;
  496.   tag[1].ti_Data = xbuf->xb_PackingMode;
  497.  
  498.   if((bufptr = (STRPTR) hookread(xbuf, XIO_READ, 0, bufsize)))
  499.   {
  500.     ret = (((RecogFunc) sem->xps_RecogFunc) (bufptr,
  501.     xbuf->xb_RMsg.xmm_FileName, bufsize, xbuf->xb_InLen, tag));
  502.     hookread(xbuf, XIO_SEEK, 0, -bufsize);
  503.   }
  504.   return ret;
  505. }
  506.  
  507. #endif /* XPKMASTER_OPEN_C */
  508.